package com.ethink.warehouse.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.ethink.framework.common.constant.CommonRespCode;
import com.ethink.framework.common.db.PageUtils;
import com.ethink.framework.common.exception.BusinessException;
import com.ethink.framework.common.web.context.SPRequestContextHolder;
import com.ethink.id.generator.IdGenerator;
import com.ethink.warehouse.api.enums.MateInventorySaleChannelChangeLogOrderStatusEnum;
import com.ethink.warehouse.api.info.MateInventorySaleChannelChangeLogInfo;
import com.ethink.warehouse.api.info.MateInventorySaleChannelChangeLogModeInfo;
import com.ethink.warehouse.api.request.MateInventorySaleChannelChangeLogAddItemRequest;
import com.ethink.warehouse.api.request.MateInventorySaleChannelChangeLogAddRequest;
import com.ethink.warehouse.api.request.MateInventorySaleChannelChangeLogQueryRequest;
import com.ethink.warehouse.api.request.MateInventorySaleChannelChangeLogUpdateRequest;
import com.ethink.warehouse.api.response.MateInventorySaleChannelChangeLogAddResponse;
import com.ethink.warehouse.api.response.MateInventorySaleChannelChangeLogDeleteResponse;
import com.ethink.warehouse.api.response.MateInventorySaleChannelChangeLogGetDetailResponse;
import com.ethink.warehouse.api.response.MateInventorySaleChannelChangeLogUpdateResponse;
import com.ethink.warehouse.common.entity.MateInventorySaleChannelChangeLog;
import com.ethink.warehouse.common.entity.MateInventorySaleChannelChangeLogDetail;
import com.ethink.warehouse.common.mapper.MateInventorySaleChannelChangeLogDetailMapper;
import com.ethink.warehouse.common.mapper.MateInventorySaleChannelChangeLogMapper;
import com.ethink.warehouse.converter.MateInventorySaleChannelChangeLogConverter;
import com.ethink.warehouse.service.MateInventorySaleChannelChangeLogService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

/**
 * 库存货权变更 Service接口实现
 *
 * @author default
 * @date 2023-01-06
 */
@Slf4j
@Service
public class MateInventorySaleChannelChangeLogServiceImpl implements MateInventorySaleChannelChangeLogService {

    @Autowired
    private MateInventorySaleChannelChangeLogMapper mateInventorySaleChannelChangeLogMapper;
    @Autowired
    private MateInventorySaleChannelChangeLogDetailMapper mateInventorySaleChannelChangeLogDetailMapper;
    @Autowired
    private MateInventorySaleChannelChangeLogConverter mateInventorySaleChannelChangeLogConverter;
    @Autowired
    private IdGenerator idGenerator;

    @Override
    public Page<MateInventorySaleChannelChangeLogInfo> queryMateInventorySaleChannelChangeLog(MateInventorySaleChannelChangeLogQueryRequest request) {
        return mateInventorySaleChannelChangeLogMapper.queryMateInventorySaleChannelChangeLog(PageUtils.buildPage(request), request);
    }

    @Override
    public MateInventorySaleChannelChangeLogGetDetailResponse getMateInventorySaleChannelChangeLogById(Long id) {
        MateInventorySaleChannelChangeLogGetDetailResponse response = new MateInventorySaleChannelChangeLogGetDetailResponse();
        MateInventorySaleChannelChangeLogInfo main = mateInventorySaleChannelChangeLogMapper.getMateInventorySaleChannelChangeLogById(id);
        response.setMain(main);
        response.setItems(mateInventorySaleChannelChangeLogDetailMapper.queryByOrderNo(main.getOrderNo()));
        return response;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public MateInventorySaleChannelChangeLogAddResponse addMateInventorySaleChannelChangeLog(MateInventorySaleChannelChangeLogAddRequest request) {
        MateInventorySaleChannelChangeLogAddResponse response = new MateInventorySaleChannelChangeLogAddResponse();
        MateInventorySaleChannelChangeLog main = new MateInventorySaleChannelChangeLog();
        BeanUtils.copyProperties(request, main);
        main.setOrderNo(idGenerator.hqbg());
        mateInventorySaleChannelChangeLogMapper.insert(main);
        for (MateInventorySaleChannelChangeLogAddItemRequest item : request.getItems()) {
            MateInventorySaleChannelChangeLogDetail detail = new MateInventorySaleChannelChangeLogDetail();
            detail.setExceptCostPrice(item.getExceptCostPrice());
            detail.setExceptSaleTime(item.getExceptSaleTime());
            detail.setBeforeMateInventoryId(item.getBeforeMateInventoryId());
            detail.setQty(item.getQty());
            detail.setAfterSaleSubChannel(request.getAfterSaleSubChannel());
            detail.setOrderNo(main.getOrderNo());
            mateInventorySaleChannelChangeLogDetailMapper.insert(detail);
        }
        response.setId(main.getId());
        return response;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public MateInventorySaleChannelChangeLogUpdateResponse updateMateInventorySaleChannelChangeLog(MateInventorySaleChannelChangeLogUpdateRequest request) {
        MateInventorySaleChannelChangeLogUpdateResponse response = new MateInventorySaleChannelChangeLogUpdateResponse();
        MateInventorySaleChannelChangeLog main = mateInventorySaleChannelChangeLogMapper.selectById(request.getId());
        if (!MateInventorySaleChannelChangeLogOrderStatusEnum.S1.eq(main.getOrderStatus())) {
            throw new BusinessException(CommonRespCode.SYSTEM_ERR, "当前订单状态无法编辑");
        }
        LambdaUpdateWrapper<MateInventorySaleChannelChangeLog> updateWrapper = new LambdaUpdateWrapper<>();
        updateWrapper.eq(MateInventorySaleChannelChangeLog::getId, request.getId());
        updateWrapper.set(MateInventorySaleChannelChangeLog::getSubWarehouseCode, request.getSubWarehouseCode());
        updateWrapper.set(MateInventorySaleChannelChangeLog::getOrderStatus, request.getOrderStatus());
        updateWrapper.set(MateInventorySaleChannelChangeLog::getRemark, request.getRemark());
        mateInventorySaleChannelChangeLogMapper.update(null, updateWrapper);
        mateInventorySaleChannelChangeLogDetailMapper.delete(new LambdaQueryWrapper<MateInventorySaleChannelChangeLogDetail>()
                .eq(MateInventorySaleChannelChangeLogDetail::getOrderNo, main.getOrderNo())
        );
        for (MateInventorySaleChannelChangeLogAddItemRequest item : request.getItems()) {
            MateInventorySaleChannelChangeLogDetail detail = new MateInventorySaleChannelChangeLogDetail();
            detail.setExceptCostPrice(item.getExceptCostPrice());
            detail.setExceptSaleTime(item.getExceptSaleTime());
            detail.setBeforeMateInventoryId(item.getBeforeMateInventoryId());
            detail.setQty(item.getQty());
            detail.setAfterSaleSubChannel(request.getAfterSaleSubChannel());
            detail.setOrderNo(main.getOrderNo());
            mateInventorySaleChannelChangeLogDetailMapper.insert(detail);
        }
        response.setId(main.getId());
        return response;
    }

    @Override
    public MateInventorySaleChannelChangeLogDeleteResponse deleteMateInventorySaleChannelChangeLog(Long id) {
        MateInventorySaleChannelChangeLogDeleteResponse response = new MateInventorySaleChannelChangeLogDeleteResponse();
        MateInventorySaleChannelChangeLog changeLog = mateInventorySaleChannelChangeLogMapper.selectById(id);
        if (MateInventorySaleChannelChangeLogOrderStatusEnum.S3.eq(changeLog.getOrderStatus())) {
            throw new BusinessException(CommonRespCode.SYSTEM_ERR, "订单已完成，无法撤销");
        }
        LambdaUpdateWrapper<MateInventorySaleChannelChangeLog> updateWrapper = new LambdaUpdateWrapper<>();
        updateWrapper.eq(MateInventorySaleChannelChangeLog::getId, id);
        updateWrapper.set(MateInventorySaleChannelChangeLog::getIsDeleted, true);
        mateInventorySaleChannelChangeLogMapper.update(null, updateWrapper);
        mateInventorySaleChannelChangeLogDetailMapper.update(null,
                new LambdaUpdateWrapper<MateInventorySaleChannelChangeLogDetail>()
                        .eq(MateInventorySaleChannelChangeLogDetail::getOrderNo, changeLog.getOrderNo())
                        .set(MateInventorySaleChannelChangeLogDetail::getIsDeleted, true)
        );
        response.setId(changeLog.getId());
        return response;
    }

    @Override
    public void approvedMateInventorySaleChannelChangeLog(Long id) {
        LambdaUpdateWrapper<MateInventorySaleChannelChangeLog> updateWrapper = new LambdaUpdateWrapper<>();
        updateWrapper.eq(MateInventorySaleChannelChangeLog::getId, id);
        updateWrapper.set(MateInventorySaleChannelChangeLog::getOrderStatus, MateInventorySaleChannelChangeLogOrderStatusEnum.S3.getIntValue())
                .set(MateInventorySaleChannelChangeLog::getAuditUserCode, SPRequestContextHolder.getCurrentSystemUserLoginName())
                .set(MateInventorySaleChannelChangeLog::getAuditUserName, SPRequestContextHolder.getCurrentSystemUserRealName());
        mateInventorySaleChannelChangeLogMapper.update(null, updateWrapper);
    }

    @Override
    public void refuseMateInventorySaleChannelChangeLog(Long id) {
        LambdaUpdateWrapper<MateInventorySaleChannelChangeLog> updateWrapper = new LambdaUpdateWrapper<>();
        updateWrapper.eq(MateInventorySaleChannelChangeLog::getId, id);
        updateWrapper.set(MateInventorySaleChannelChangeLog::getOrderStatus, MateInventorySaleChannelChangeLogOrderStatusEnum.S1.getIntValue())
                .set(MateInventorySaleChannelChangeLog::getAuditUserCode, SPRequestContextHolder.getCurrentSystemUserLoginName())
                .set(MateInventorySaleChannelChangeLog::getAuditUserName, SPRequestContextHolder.getCurrentSystemUserRealName());
        mateInventorySaleChannelChangeLogMapper.update(null, updateWrapper);
    }

    /**
     * 货权变更货品模式分页查询
     *
     * @param request
     * @return
     */
    @Override
    public Page<MateInventorySaleChannelChangeLogModeInfo> queryMateInventorySaleChannelChangeModeLog(MateInventorySaleChannelChangeLogQueryRequest request) {
        return mateInventorySaleChannelChangeLogMapper.queryMateInventorySaleChannelChangeModeLog(PageUtils.buildPage(request), request);
    }
}
